import 'dart:convert';
import 'dart:typed_data';

import 'package:base_flutter/base_flutter.dart';
import 'package:decimal/decimal.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:ls_work/net/response/food_sample/food_sample_detail_response.dart';
import 'package:ls_work/res/colors.dart';

import 'package:flutter/cupertino.dart';

import 'package:base_flutter/base_flutter.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:ls_work/res/colors.dart';
import 'package:ls_work/util/native_toast.dart';

import '../a_elder/models/code_value_entity.dart';
import '../model/food_sample/food_sample_submit_data.dart';
import '../net/response/food/regular_week_menu_list_data.dart';
import '../net/response/food/week_menu_list_data.dart';
import '../print/week_print_data.dart';

extension DateTimeExt on DateTime {
  bool isInTimeRange({required String startTime, required String endTime}) {
    var start = startTime.toDate();
    var end = endTime.toDate();
    return this.isAfter(start!) && this.isBefore(end!);
  }
}

extension StringsExt on String {
  ///json字符串转map
  Map<String, dynamic> toMap() {
    return jsonDecode(this);
  }

  Pattern toReg() {
    return RegExp(this);
  }

  String ifEmpty(String place) {
    return this.isEmpty ? place : this;
  }

  bool get isChinese => RegExp('[\u4e00-\u9fa5]').hasMatch(this);

  bool isBeforeNow() {
    var date = this.toDate();
    if (date == null) {
      return false;
    }
    return DateTime.now().isBefore(date);
  }

  String formatDateStr(
      {List<String> format = const [
        "yyyy",
        '-',
        'mm',
        '-',
        'dd',
        ' ',
        'HH',
        ':',
        'nn',
        ':',
        'ss'
      ]}) {
    try {
      var date = this.toDate();
      return date?.toDateStr(format) ?? "";
    } catch (e) {
      return this;
    }
  }

  String timeTypeStr() {
    if (this == "1") {
      return "早餐";
    }
    if (this == '2') {
      return '午餐';
    }
    if (this == '3') {
      return '晚餐';
    }
    return '';
  }

  int toInteger({int radix = 10}) {
    return int.tryParse(this, radix: radix) ?? 0;
  }

  String changeTime({List<String> format = const <String>[HH, ':', nn]}) {
    if (this.isNullOrEmpty()) {
      return "";
    }
    try {
      var date = DateTime.parse(this);
      return date.toDateStr(format);
    } catch (E) {
      return this;
    }
  }
}

// extension ListExr on List<Widget> {
//   List<Widget> insertWidget(Widget widget) {
//     Iterator<Widget> iterator = this.iterator;
//     var items = <Widget>[];
//
//     if (!iterator.moveNext()) return [];
//     items.add(iterator.current);
//     while (iterator.moveNext()) {
//       items.add(widget);
//       items.add(iterator.current);
//     }
//     return items;
//   }
// }

extension ListExInfo on List {
  List<T> takeWhere<T>(bool test(T element)) {
    var list = <T>[];
    for (var item in this) {
      if (test(item)) {
        list.add(item);
      }
    }
    return list;
  }
}

extension dynamicExt on dynamic {
  String get netError => NetErrorUtils.getNetError(this);

  String? toStringOrNull() {
    return this == null ? null : this.toString();
  }
}

extension numExt on num? {
  String toNumStr({String placeHold = ""}) =>
      this == null ? placeHold : this.toString();

  Decimal? get d => this == null ? null : Decimal.parse(this.toString());
}

extension numNExt on num {
  String toNumStr({String placeHold = ""}) => this.toString();

  Decimal get d => Decimal.parse(this.toString());
}

extension doubleExt on double? {
  String toNumStr({String placeHold = ""}) =>
      this == null ? placeHold : this.toString();
}

showApplyDialog(
    {required BuildContext context,
    String title = "",
    String message = "",
    String applyText = "确定",
    required Function() onSubmit}) {
  showCupertinoDialog(
      context: context,
      builder: (context) {
        return CupertinoAlertDialog(
          title: title.isNullOrEmpty()
              ? null
              : CommonText(title).addToContainer(
                  alignment: Alignment.center,
                  margin: EdgeInsets.only(bottom: 10)),
          content:
              CommonText(message).addToContainer(alignment: Alignment.center),
          actions: [
            TextButton(
                onPressed: () {
                  Navigator.pop(context);
                },
                child: CommonText('取消', textColor: Colors.grey)),
            TextButton(
                onPressed: () {
                  Navigator.pop(context);
                  onSubmit();
                },
                child: CommonText(applyText, textColor: Colours.app_main))
          ],
        );
      });
}

extension HexColor on Color {
  /// String is in the format "aabbcc" or "ffaabbcc" with an optional leading "#".
  static Color? fromHex(String hexString) {
    final buffer = StringBuffer();
    if (hexString.length == 6 || hexString.length == 7) buffer.write('ff');
    buffer.write(hexString.replaceFirst('#', ''));
    try {
      return Color(int.parse(buffer.toString(), radix: 16));
    } catch (e) {
      return null;
    }
  }

  /// Prefixes a hash sign if [leadingHashSign] is set to `true` (default is `true`).
  String toHex({bool leadingHashSign = true}) => '${leadingHashSign ? '#' : ''}'
      '${alpha.toRadixString(16).padLeft(2, '0')}'
      '${red.toRadixString(16).padLeft(2, '0')}'
      '${green.toRadixString(16).padLeft(2, '0')}'
      '${blue.toRadixString(16).padLeft(2, '0')}';
}

extension WeekMenuExt on List<WeekMenuContent> {
  List<WeekPrintData> toPrintData(String startDate) {
    var dateTime = DateTime.parse(startDate);
    var format = ["yyyy", "-", "mm", "-", "dd"];
    var list = <WeekPrintData>[];
    for (var menu in this) {
      for (var categary in (menu.ruleCategory ?? <RuleCategory>[])) {
        for (var date in (categary.goodsInfo ?? <GoodsInfo>[])) {
          var data = WeekPrintData(
              weekDay: date.weekDay, timeSection: menu.timeSection);
          var foodDate = dateTime.add(Duration(days: (date.weekDay ?? 0) - 1));
          data.date = foodDate.toDateStr(format);
          if (!date.selectItems.isEmpty) {
            if (!list.contains(data)) {
              var categaryList = <CategaryList>[
                CategaryList(
                    categary: categary.categary, goodsList: date.selectItems)
              ];
              data.categaryList = categaryList;
              list.add(data);
            } else {
              var index = list.indexOf(data);

              (list[index].categaryList ?? []).add(CategaryList(
                  categary: categary.categary, goodsList: date.selectItems));
            }
          }
        }
      }
    }
    return list;
  }
}

extension CodeValueExt on String {
  String codeValueStr(List<CodeValue> foodTimes) {
    var value = "";
    for (var item in foodTimes) {
      if (item.codeValue == this) {
        value = item.name;
        break;
      }
    }
    return value;
  }
}

extension FoodSampleExt on FoodSampleDetailResponse {
  FoodSampleSubmitData toSubmitData(List<CodeValue> foodTimes) {
    var data = FoodSampleSubmitData(
      id: id,
      sampleNo: sampleNo ?? "",
      sterDate: sterDate ?? "",
      sampleDate: sampleDate ?? "",
      destroyedDate: destroyedDate ?? "",
    );
    data.details = (details ?? []).map((e) {
      return FoodSampleSubmitDetail(
          id: e.id,
          label: e.label,
          category: e.category,
          foodName: e.foodName,
          sampleVolume: e.sampleVolume,
          categoryName: e.category?.codeValueStr(foodTimes),
          attachList: (e.attachList ?? []).map((e) => e.attachId!).toList());
    }).toList();

    return data;
  }
}

extension RegularWeekMenuExt on List<RegularWeekMenuContent> {
  List<WeekPrintData> toPrintData(String startDate) {
    var dateTime = DateTime.parse(startDate);
    var format = ["yyyy", "-", "mm", "-", "dd"];
    var list = <WeekPrintData>[];
    for (var menu in this) {
      for (var date in (menu.goodsInfo ?? <GoodsInfo>[])) {
        var data =
            WeekPrintData(weekDay: date.weekDay, timeSection: menu.timeSection);
        var foodDate = dateTime.add(Duration(days: (date.weekDay ?? 0) - 1));
        data.date = foodDate.toDateStr(format);
        if (!date.selectItems.isEmpty) {
          if (!list.contains(data)) {
            var categaryList = <CategaryList>[
              CategaryList(categary: "", goodsList: date.selectItems)
            ];
            data.categaryList = categaryList;
            list.add(data);
          } else {
            var index = list.indexOf(data);

            (list[index].categaryList ?? [])
                .add(CategaryList(categary: "", goodsList: date.selectItems));
          }
        }
      }
    }
    return list;
  }
}

extension ColorExt on Color {
  /// 颜色检测只保存 #RRGGBB格式 FF透明度
  /// [color] 格式可能是材料风/十六进制/string字符串
  /// 返回[String] #rrggbb 字符串
  String color2HEX() {
    var str = "";
    //将十进制转换成为16进制 返回字符串但是没有0x开头
    String temp = this.value.toRadixString(16);
    str = "#${temp.substring(2, 8)}";
    return str;
  }
}

extension Uint8ListExt on Uint8List {
  Uint8List addZero({int count = 128}) {
    var list = <int>[];
    list.addAll(this);
    do {
      list.add(0);
    } while (list.length < 128);
    return Uint8List.fromList(list);
  }
}

Decimal maxD(Decimal a, Decimal b) {
  if (a > b) {
    return a;
  } else {
    return b;
  }
}

extension BuildContextExt on BuildContext {
  Size get screenSize => MediaQuery.of(this).size;
}

Future<bool> isAndroid13OrAbove() async {
  var sdkInt = await NativeUtils.androidSdkInt();
  return (sdkInt??0) >= 33; // Android 13是API 33
}
